﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Web.UI;
using System.Web.UI.WebControls;
using CustomerContactSystem.Core.Infrastructure.Configuration;
using CustomerContactSystem.Core.Infrastructure.DataAccess;
using CustomerContactSystem.Core.Infrastructure.Domain;
using CustomerContactSystem.Core.Infrastructure.Email;
using CustomerContactSystem.Core.Model;
using StructureMap;

namespace CustomerContactSystem.WebForms {
    public class BasePage : Page {
        public IApplicationSettings ConfigSettings { get { return SiteMaster.ConfigSettings; } }
        public IEmailService EmailService { get; set; }
        public INhibernateRepository<Customer> CustomerRepository { get; set; }
        public INhibernateRepository<Department> DepartmentRepository { get; set; }
        public INhibernateRepository<Enquiry> EnquiryRepository { get; set; }
        public INhibernateRepository<EnquiryCategory> EnquiryCategoryRepository { get; set; }
        public INhibernateRepository<EnquiryClassification> EnquiryClassificationRepository { get; set; }
        public INhibernateRepository<EnquiryClosure> EnquiryClosureRepository { get; set; }
        public INhibernateRepository<EnquiryCommitmentClosure> EnquiryCommitmentClosureRepository { get; set; }
        public INhibernateRepository<EnquiryCurrentReferral> EnquiryCurrentReferralRepository { get; set; }
        public INhibernateRepository<EnquiryDeletion> EnquiryDeletionRepository { get; set; }
        public INhibernateRepository<EnquiryFirstReferral> EnquiryFirstReferralRepository { get; set; }
        public INhibernateRepository<EnquiryReferral> EnquiryReferralRepository { get; set; }
        public INhibernateRepository<EnquirySource> EnquirySourceRepository { get; set; }
        public INhibernateRepository<Rep> RepRepository { get; set; }
        public INhibernateRepository<Tag> TagRepository { get; set; }
        public INhibernateRepository<UserGroup> UserGroupRepository { get; set; }
        public INhibernateRepository<UserRole> UserRoleRepository { get; set; }
        public INhibernateRepository<User> UserRepository {
            get { return SiteMaster.UserRepository; }
        }

        public Site SiteMaster {
            get { return (Site)Master; }
        }

        public User LoggedUser {
            get { return SiteMaster.LoggedUser; }
        }

        public BasePage() {
            ObjectFactory.BuildUp(this);
        }

        public bool IsValidPageRequest(bool loggedUserRequired, bool ensureNotPostBack, string requiredQueryStrings) {
            if (loggedUserRequired) {
                if (LoggedUser == null) {
                    return false;
                }
            }

            if (ensureNotPostBack) {
                if (Page.IsPostBack) {
                    return false;
                }
            }

            if (!string.IsNullOrEmpty(requiredQueryStrings)) {
                var queryStringNames = requiredQueryStrings.Split(',');

                foreach (var queryStringName in queryStringNames) {
                    if (Request.QueryString[queryStringName] == null) {
                        return false;
                    }
                }
            }

            return true;
        }

        public void AddUserToSession(int userId) {
            SiteMaster.AddUserToSession(userId);
        }

        public string QueryStringOrEmpty(string paramName) {
            return Request.QueryString[paramName] ?? "";
        }

        public int QueryStringOrZero(string paramName) {
            return (Request.QueryString[paramName] != null && Request.QueryString[paramName].Length > 0) ? int.Parse(Request.QueryString[paramName]) : 0;
        }

        public int QueryStringOrNumber(string paramName, int defaultValue) {
            return (Request.QueryString[paramName] != null && Request.QueryString[paramName].Length > 0) ? int.Parse(Request.QueryString[paramName]) : defaultValue;
        }

        public bool QueryStringOrFalse(string paramName) {
            return (Request.QueryString[paramName] != null && Request.QueryString[paramName].Length > 0) && bool.Parse(Request.QueryString[paramName]);
        }

        public string QueryStringOrEmptyDate(string paramName) {
            return (Request.QueryString[paramName] != null) ? Request.QueryString[paramName].Replace("-", "/") : "";
        }

        public DateTime QueryStringOrMinDate(string paramName) {
            return (Request.QueryString[paramName] != null && Request.QueryString[paramName].Length > 0) ? DateTime.Parse(Request.QueryString[paramName].Replace("-", "/")) : DateTime.MinValue;
        }

        public void BindDropDownList(DropDownList ctrl, IEnumerable data, string textProperty, string valueProperty, string firstOption, string selectedValue)
        {
            ctrl.DataSource = data;
            if (!string.IsNullOrEmpty(textProperty))
            {
                ctrl.DataTextField = textProperty;
            }
            if (!string.IsNullOrEmpty(valueProperty))
            {
                ctrl.DataValueField = valueProperty;
            }
            ctrl.DataBind();
            if (!string.IsNullOrEmpty(firstOption))
            {
                ctrl.Items.Insert(0, new ListItem(firstOption, "0"));
            }
            ctrl.SelectedIndex = ctrl.Items.IndexOf(ctrl.Items.FindByValue(selectedValue));
        }

        public void SetDropDownListIndexFromQueryStringValue(DropDownList ctrl, string paramName)
        {
            ctrl.SelectedIndex = ctrl.Items.IndexOf(ctrl.Items.FindByValue(QueryStringOrEmpty(paramName)));
        }

        public void SetDropDownListIndexFromValue(DropDownList ctrl, string value) {
            ctrl.SelectedIndex = ctrl.Items.IndexOf(ctrl.Items.FindByValue(value));
        }

        public Int32 DropDownListValueOrZero(DropDownList ctrl) {
            return ctrl.Items.Count > 0 ? Int32.Parse(ctrl.SelectedItem.Value) : 0;
        }

        public bool IsValidObject(Entity obj, ITextControl messageLabel) {
            messageLabel.Text = "";
            var rules = obj.GetBrokenRules();
            var businessRules = rules as List<BusinessRule> ?? rules.ToList();
            if (businessRules.Any())
            {
                foreach (var businessRule in businessRules)
                {
                    messageLabel.Text += businessRule.Rule + "<br />";
                }
                return false;
            }
            return true;
        }        
    }
}